<?php
/**
 * XmuSlh, web platform of Student Association Federation of Xiamen University
 * 
 * Rewritting one or some pages of StatusNet. 
 * To get the original version, please visit <http://status.net/>.
 * 
 * StatusNet, the distributed open-source microblogging tool
 * 
 * LICENCE: This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

/**
 * The Photo class for table 'photo'.
 * 
 * @author		ytukie <ytukie@gmail.com>
 * @version		0.1
 */

// XmuSlh only.
if ( !defined('XMUSLH')) { exit(1); }

require_once INSTALLDIR . '/classes/Memcached_DataObject.php';

// Definitions.
// Column of status reserves.

// Definitions.
define('PHOTO_THUMBNAIL_MAXWIDTH',		slh_config('photo', 'thumbnail_maxwidth'));
define('PHOTO_THUMBNAIL_MAXHEIGHT',		slh_config('photo', 'thumbnail_maxheight'));

class Photo extends Memcached_DataObject
{
	public $__table = 'photo';				// table name
	public $id;								// int(11)  primary_key not_null
	public $status;							// tinyint(4)
	public $photoset_id;					// int(11)  foreign_key not_null
	public $photoname;						// varchar(255)  not_null
	public $mimetype;						// varchar(32)
	public $width;							// int(11)
	public $height;							// int(11)
	public $created;						// datetime  not_null
	
	// Static get
	function staticGet($key, $value = null)
	{
		return Memcached_DataObject::staticGet('photo', $key, $value); 
	}
	
	/**
	 * Delete the photo both in database and filesystem.
	 */
	function delete()
	{
		@unlink($this->photopath());
		@unlink($this->thumbnailpath());
		
		parent::delete();
	}
	
	/**
	 * Add the infomation of photo into database.
	 */
	static function add($fields)
	{
		// Magically put fields into current scope.
		extract($fields);
		
		$photo = new Photo();
		$photo->status = 0;
		$photo->photoset_id = $photoset_id;
		$photo->photoname = $photoname;
		$photo->mimetype = $mimetype;
		$photo->width = $width;
		$photo->height = $height;
		$photo->created = slh_sql_now();
		
		$photo_id = $photo->insert();
		if (empty($photo_id)) {
			slh_log_db_error($photo, 'INSERT', __FILE__);
			return false;
		}
		
		return $photo_id;
	}
	
	/**
	 * Get the ids as a list. Use offset and limit to control
	 * the pagination.
	 * 
	 * @param int, photoset_id the id of the specific photoset.
	 */
	static function getIdsByPhotosetIdList($photoset_id, 
										   $offset = 0,
								 		   $limit = 0)
	{
		$photo = new Photo();
		$photo->photoset_id = $photoset_id;
		
		$photo->selectAdd();
		$photo->selectAdd('id');
		$photo->selectAdd('photoset_id');
		
		$photo->whereAdd('photoset_id in (SELECT `id` FROM `photoset`)');
		
		$photo->orderBy('created DESC');
		
		if ( !is_null($offset)) {
			$photo->limit($offset, $limit);
		}
		
		$ids = array();
		if ($photo->find()) {
			while ($photo->fetch()) {
				$ids[] = $photo->id;
			}
		}
		
		$photo->free();
		$photo = NULL;
		
		return $ids;
	}
	
	/**
	 * Get the special ids of the photos.
	 * 
	 * Usually the list with pagination.
	 */
	static function getPhotosByIds($ids)
	{
		$cache = Cache::instance();
		
		if ( !empty($cache)) {
			$photos = array();
			foreach ($ids as $id) {
				$p = Photo::staticGet('id', $id);
				if ( !empty($p)) {
					$photos[] = $p;
				}
			}
			
			return new ArrayWrapper($photos);
		} else {
			// Miss the cache.
			$photos = new Photo();
			if (empty($ids)) {
				return $photos;
			}
			
			$photos->whereAdd('id in (' . implode(', ', $ids) . ')');
			$photos->find();
			
			$temp = array();
			while ($photos->fetch()) {
				$temp[$photos->id] = clone($photos);
			}
			
			$wrapped = array();
			
			foreach($ids as $id) {
				if (array_key_exists($id, $temp)) {
					$wrapped[] = $temp[$id];
				}
			}
			
			return new ArrayWrapper($wrapped);
		}
	}
	
	/**
	 * Get the thumbnail url by given id.
	 */
	static function getThumbnailUrlById($id)
	{
		$query = 'SELECT `photoname` FROM `photo` ' .
				 'WHERE `id` = ' . $id;
		
		$photo = new Photo();
		$photo->query($query);
		
		$result = false;
		if ($photo->fetch()) {
			$result = Photo::url(Photo::filename2Thumbnailname($photo->photoname));
		}
		
		$photo->free();
		$photo = null;
		
		return $result;
	}
	
	/**
	 * Get the photo path.
	 */
	function photopath()
	{
		return Photo::path($this->photoname);
	}
	
	/**
	 * Get the photo url.
	 */
	function photourl()
	{
		return Photo::url($this->photoname);
	}
	
	/**
	 * Get the thumbnail path.
	 */
	function thumbnailpath()
	{
		return Photo::path(Photo::filename2Thumbnailname($this->photoname));
	}
	
	/**
	 * Get the thumbnail url.
	 */
	function thumbnailurl()
	{
		return Photo::url(Photo::filename2Thumbnailname($this->photoname));
	}
	
	/**
	 * Change to original filename(photoname) to thumbnail name.
	 */
	static function filename2Thumbnailname($filename)
	{
		return strtr($filename, array('original' => 'thumbnail'));
	}
	
	/**
	 * The barename of the original file.
	 */
	static function filename($id, 
							 $extension, 
							 $extra = null)
	{
		return 'original-' . $id . (($extra) ? ('-' . $extra) : '') . $extension;
	}
	
	/**
	 * The absolute path including the barename. (../xx.jpg).
	 */
	static function path($filename)
	{
		$dir = slh_config('photo', 'dir');
		
		if ($dir[strlen($dir) - 1] != '/') {
			$dir .= '/';
		}
		
		return $dir . $filename;
	}
	
	/**
	 * The unique url.
	 */
	static function url($filename)
	{
		$path = slh_config('photo', 'path');
		
		if ($path[strlen($path) - 1] != '/') {
			$path .= '/';
		}
		
		if ($path[0] != '/') {
			$path = '/' . $path;
		}
		
		// FIXME: The extra server for avatar.
		$server = slh_config('photo', 'server');
		
		return 'http://' . $server . $path . $filename;
	}
	
	// Fake default image.
	static function defaultPhoto()
	{
		return slh_config('photo', 'path') . 'default.jpg';
	}
}
?>